
#include "stdafx.h"
#include "PGLNet.h"
#using <System.dll>
#using <System.Drawing.dll>
#using <System.Web.dll>
#using <System.Xml.dll>


using namespace System;
using namespace System::Runtime::InteropServices;
using namespace System::Runtime::CompilerServices;
using namespace System::Runtime::Serialization;

#ifdef _DEBUG
#define PGLDLL_NAME "pglmfc7d.dll"
#else
#define PGLDLL_NAME "pglmfc7.dll"
#endif

#define PTR2CHR(p)        (static_cast<char*>(p.ToPointer()))
#define PTR2VOID(p)        (static_cast<void*>(p.ToPointer()))
#define PTR2FLOAT(p)        (static_cast<float[]>(p.ToPointer()))
#define PTR2FLOATPTR(p)        (static_cast<float*>(p.ToPointer()))

namespace PGLNet
{

    ///<summary>Handles initialization and clean-up of the PGL library.</summary>
    [Serializable]
    public __gc  class PglLoader : public ISerializable
	{
	public:
        ///<summary>Initializes COM and GDI+</summary>
        ///<param name="startCOM"></param>
        ///<param name="startGDIp"></param>
		PglLoader(
			bool startCOM,
			bool startGDIp
			)	
		{	
			m_startCOM=startCOM;
			m_loaded= Init(startCOM,startGDIp) >0;
			if (!m_loaded)
				throw new System::Exception(
					"Could not initialized PGL or GDI+"
					);
		};
		~PglLoader()	{	UnLoad(); };

        ///<summary></summary>
		__property bool get_Loaded() {	return m_loaded;};
        ///<summary></summary>
		void UnLoad()
		{
			if (m_loaded)
			{
				Quit(m_startCOM);
				m_loaded=false;
			}
        }

        void GetObjectData(SerializationInfo* info, StreamingContext context) 
        {
            info->AddValue("loaded",m_loaded);
            info->AddValue("startcom",m_startCOM);
        }

	private:
		bool m_loaded;
		bool m_startCOM;

		[ DllImport(PGLDLL_NAME, EntryPoint="pglInit") ]
		static public int Init(int bInitGDIp, int bInitCOM);
		[DllImport(PGLDLL_NAME, EntryPoint="pglQuit")]
		static public int Quit(int bCloseCOM);
	};

    ///<summary></summary>
	public __value  struct Pgl
	{
	public:
        ///<summary>Create a new dialog windows</summary>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglFigure")]
		static public long Figure();

        ///<summary></summary>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglRegion")]
		static public long Region();

        ///<summary></summary>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglGetCR")]
		static public long GetCR();

        ///<summary></summary>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglSetCR")]
		static public int  SetCR(long dwRegionID);

        ///<summary></summary>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglGetCD")]
		static public long GetCD();

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglDoModalRegion")]
		static public int DoModalRegion(
            long lRegionID, 
            [MarshalAs(UnmanagedType::LPStr)]String* szFlags
            );

        ///<summary></summary>
        ///<param name=""></param>
		[DllImport(PGLDLL_NAME, EntryPoint="pglCloseFigure")]
		static public void CloseFigure( long lID);

        ///<summary></summary>
		[DllImport(PGLDLL_NAME, EntryPoint="pglCloseAllFigures")]
		static public void CloseAllFigures();

        ///<summary></summary>
        ///<param name=""></param>
		[DllImport(PGLDLL_NAME, EntryPoint="pglCloseRegion")]
		static public void CloseRegion( long lRegionID);

        ///<summary></summary>
		[DllImport(PGLDLL_NAME, EntryPoint="pglCloseAllRegions")]
		static public void CloseAllRegions();

        ///<summary></summary>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglGetObjectsSize")]
		static public long GetObjectsSize( long lRegionID);

        ///<summary></summary>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglGetObject")]
		static public long GetObject( long lRegionID, long uIndex );

        ///<summary></summary>
        ///<param name=""></param>
		[DllImport(PGLDLL_NAME, EntryPoint="pglRemoveObject")]
		static public void RemoveObject( long lRegionID, long uIndex );

        ///<summary></summary>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglGetChildrenSize")]
		static public long GetChildrenSize( long lRegionID );

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglGetChild")]
		static public long GetChild( long lRegionID, long uIndex );

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
		[DllImport(PGLDLL_NAME, EntryPoint="pglRemoveChild")]
		static public void RemoveChild( long lRegionID, long uIndex );

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglDivide")]
		static public long Divide(
            long lRegionID, 
            long nRows, 
            long nCols
            );

        ///<summary></summary>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglLayout")]
		static public long Layout(
            long lRegionID, 
            [MarshalAs(UnmanagedType::LPStr)]String* szLayout
            );

        ///<summary></summary>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglGetParent")]
		static public long GetParent(long lObjectID );

        ///<summary></summary>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglOutOfChild")]
		static public long OutOfChild();

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglPlot")]
		static public long Plot(
			long lRegionID, 
			long nPoints, 
            [MarshalAs(UnmanagedType::LPArray, SizeParamIndex=1)] float  pX __gc[],
			[MarshalAs(UnmanagedType::LPArray, SizeParamIndex=1)]  float pY __gc[], 
			[MarshalAs(UnmanagedType::LPStr)]String* szFlags,
            int makeCopy
            );

        [DllImport(PGLDLL_NAME, EntryPoint="pglPlot")]
        static public long Plot(
            long lRegionID, 
            long nPoints, 
            float* pX,
            float* pY, 
            [MarshalAs(UnmanagedType::LPStr)]String* szFlags,
            int makeCopy
            );

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglPlotY")]
		static public long PlotY(
			long lRegionID, 
			long nPoints, 
			float fX0, float 
			fXStep,
			[MarshalAs(UnmanagedType::LPArray, SizeParamIndex=1)] float pY __gc[], 
            [MarshalAs(UnmanagedType::LPStr)]String* szFlags,
            int makeCopy
            );

        [DllImport(PGLDLL_NAME, EntryPoint="pglPlotY")]
        static public long PlotY(
            long lRegionID, 
            long nPoints, 
            float fX0, float 
            fXStep,
            float* pY, 
            [MarshalAs(UnmanagedType::LPStr)]String* szFlags,
            int makeCopy
            );

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglPlotLOD")]
		static public long PlotLOD(
			long lRegionID, 
			long nPoints,
			[MarshalAs(UnmanagedType::LPArray,SizeParamIndex=1)] float pX  __gc[],
			[MarshalAs(UnmanagedType::LPArray, SizeParamIndex=1)] float pY __gc[], 
			float fCompressionRatio, 
            [MarshalAs(UnmanagedType::LPStr)]String* szFlags,
            int makeCopy
            );

        [DllImport(PGLDLL_NAME, EntryPoint="pglPlotLOD")]
        static public long PlotLOD(
            long lRegionID, 
            long nPoints,
            float* pX,
            float* pY, 
            float fCompressionRatio, 
            [MarshalAs(UnmanagedType::LPStr)]String* szFlags,
            int makeCopy
            );

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglPlotLODY")]
		static public long PlotLODY(
			long lRegionID, 
			long nPoints,
			float fX0, 
			float fXStep,
			[MarshalAs(UnmanagedType::LPArray, SizeParamIndex=1)] float pY __gc[] , 
			float fCompressionRatio, 
            [MarshalAs(UnmanagedType::LPStr)]String* szFlags,
            int makeCopy
            );

        [DllImport(PGLDLL_NAME, EntryPoint="pglPlotLODY")]
        static public long PlotLODY(
            long lRegionID, 
            long nPoints,
            float fX0, 
            float fXStep,
            float* pY, 
            float fCompressionRatio, 
            [MarshalAs(UnmanagedType::LPStr)]String* szFlags,
            int makeCopy
            );

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglPlotFcn")]
		static public long PlotFcn(
			long lRegionID, 
			long nPoints,
			[MarshalAs(UnmanagedType::LPArray, SizeParamIndex=1)] float pX __gc[], 
			[MarshalAs(UnmanagedType::LPStr)]String* szFcnX,
			[MarshalAs(UnmanagedType::LPStr)]String* szFlags,
            int makeCopy
            );

        [DllImport(PGLDLL_NAME, EntryPoint="pglPlotFcn")]
        static public long PlotFcn(
            long lRegionID, 
            long nPoints,
            float* pX, 
            [MarshalAs(UnmanagedType::LPStr)]String* szFcnX,
            [MarshalAs(UnmanagedType::LPStr)]String* szFlags,
            int makeCopy
            );

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglPlotFcnY")]
		static public long PlotFcnY(
			long lRegionID, 
			long nPoints, 
			float fX0, 
			float fXStep, 
			[MarshalAs(UnmanagedType::LPStr)]String* szFcnX, 
            [MarshalAs(UnmanagedType::LPStr)]String* szFlags,
            int makeCopy
            );

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglPlotHor")]
		static public long PlotHor(
			long lRegionID, 
			float fY, 
			[MarshalAs(UnmanagedType::LPStr)]String* szFlags);

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglPlotVer")]
		static public long PlotVer(
			long lRegionID, 
			float fX, 
			[MarshalAs(UnmanagedType::LPStr)]String* szFlags);

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglHistogram")]
		static public long Histogram(
			long lRegionID, 
			long nPoints,
			[MarshalAs(UnmanagedType::LPArray, SizeParamIndex=1)] float pY __gc[], 
            [MarshalAs(UnmanagedType::LPStr)]String* szFlags,
            int makeCopy
            );

        [DllImport(PGLDLL_NAME, EntryPoint="pglHistogram")]
        static public long Histogram(
            long lRegionID, 
            long nPoints,
            float* pY, 
            [MarshalAs(UnmanagedType::LPStr)]String* szFlags,
            int makeCopy
            );

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglErrorBar")]
		static public long ErrorBar(
			long lRegionID, 
			long nPoints,
			[MarshalAs(UnmanagedType::LPArray, SizeParamIndex=1)] float pX __gc[],
			[MarshalAs(UnmanagedType::LPArray, SizeParamIndex=1)] float pY __gc[],
			[MarshalAs(UnmanagedType::LPArray, SizeParamIndex=1)] float pErrorUp __gc[],
			[MarshalAs(UnmanagedType::LPArray, SizeParamIndex=1)] float pErrorDown __gc[], 
            [MarshalAs(UnmanagedType::LPStr)]String* szFlags,
            int makeCopy
            );

        [DllImport(PGLDLL_NAME, EntryPoint="pglErrorBar")]
        static public long ErrorBar(
            long lRegionID, 
            long nPoints,
            float* pX,
            float* pY,
            float* pErrorUp,
            float* pErrorDown, 
            [MarshalAs(UnmanagedType::LPStr)]String* szFlags,
            int makeCopy
            );

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglErrorBarY")]
		static public long ErrorBarY(
			long lRegionID, 
			long nPoints, 
			float fX0, 
			float fXStep,
			[MarshalAs(UnmanagedType::LPArray, SizeParamIndex=1)] float pY __gc[],
			[MarshalAs(UnmanagedType::LPArray, SizeParamIndex=1)] float pErrorUp __gc[],
			[MarshalAs(UnmanagedType::LPArray, SizeParamIndex=1)] float pErrorDown __gc[], 
            [MarshalAs(UnmanagedType::LPStr)]String* szFlags,
            int makeCopy
            );

        [DllImport(PGLDLL_NAME, EntryPoint="pglErrorBarY")]
        static public long ErrorBarY(
            long lRegionID, 
            long nPoints, 
            float fX0, 
            float fXStep,
            float* pY,
            float* pErrorUp,
            float* pErrorDown, 
            [MarshalAs(UnmanagedType::LPStr)]String* szFlags,
            int makeCopy
            );

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglScatter")]
		static public long Scatter(
			long lRegionID, 
			long nPoints,
			[MarshalAs(UnmanagedType::LPArray, SizeParamIndex=1)] float pX __gc[],
			[MarshalAs(UnmanagedType::LPArray, SizeParamIndex=1)] float pY __gc[],
			[MarshalAs(UnmanagedType::LPArray, SizeParamIndex=1)] float pValues __gc[], 
            [MarshalAs(UnmanagedType::LPStr)]String* szFlags,
            int makeCopy
            );

        [DllImport(PGLDLL_NAME, EntryPoint="pglScatter")]
        static public long Scatter(
            long lRegionID, 
            long nPoints,
            float* pX,
            float* pY,
            float* pValues, 
            [MarshalAs(UnmanagedType::LPStr)]String* szFlags,
            int makeCopy
            );

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglStock")]
		static public long Stock(
			long lRegionID, 
			long nPoints, 
			float fX0, 
			float fXStep,
			[MarshalAs(UnmanagedType::LPArray, SizeParamIndex=1)] float pOpen __gc[],
			[MarshalAs(UnmanagedType::LPArray, SizeParamIndex=1)] float pHigh __gc[],
			[MarshalAs(UnmanagedType::LPArray, SizeParamIndex=1)] float pLow __gc[],
			[MarshalAs(UnmanagedType::LPArray, SizeParamIndex=1)] float pClose __gc[], 
            [MarshalAs(UnmanagedType::LPStr)]String* szFlags,
            int makeCopy
            );

        [DllImport(PGLDLL_NAME, EntryPoint="pglStock")]
        static public long Stock(
            long lRegionID, 
            long nPoints, 
            float fX0, 
            float fXStep,
            float* pOpen,
            float* pHigh,
            float* pLow,
            float* pClose, 
            [MarshalAs(UnmanagedType::LPStr)]String* szFlags,
            int makeCopy
            );

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglCandleStick")]
		static public long CandleStick(
			long lRegionID, 
			long nPoints, 
			float fX0, 
			float fXStep,
			[MarshalAs(UnmanagedType::LPArray, SizeParamIndex=1)] float pOpen __gc[],
			[MarshalAs(UnmanagedType::LPArray, SizeParamIndex=1)] float pHigh __gc[],
			[MarshalAs(UnmanagedType::LPArray, SizeParamIndex=1)] float pLow __gc[],
			[MarshalAs(UnmanagedType::LPArray, SizeParamIndex=1)] float pClose __gc[], 
            [MarshalAs(UnmanagedType::LPStr)]String* szFlags,
            int makeCopy
            );

        [DllImport(PGLDLL_NAME, EntryPoint="pglCandleStick")]
        static public long CandleStick(
            long lRegionID, 
            long nPoints, 
            float fX0, 
            float fXStep,
            float* pOpen,
            float* pHigh,
            float* pLow,
            float* pClose, 
            [MarshalAs(UnmanagedType::LPStr)]String* szFlags,
            int makeCopy
            );

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglImage")]
		static public long Image(
			long lRegionID, 
			[MarshalAs(UnmanagedType::LPStr)]String* szFileName, 
			[MarshalAs(UnmanagedType::LPStr)]String* szFlags);

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
		[DllImport(PGLDLL_NAME, EntryPoint="pglSet")]
		static public void Set(
            long uObjectID, 
            [MarshalAs(UnmanagedType::LPStr)]String* szPropAndValues);

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
		[DllImport(PGLDLL_NAME, EntryPoint="pglGet")]
		static public void Get(
            long uObjectID, 
            [MarshalAs(UnmanagedType::LPStr)]String* szProperty, 
            char** ppStr);

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
		[DllImport(PGLDLL_NAME, EntryPoint="pglGetHelp")]
		static public void GetHelp(long uObjectID, char** ppStr);

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
        [DllImport(PGLDLL_NAME, EntryPoint="pglLeftLabel")]
		static public long LeftLabel(
            long lRegionID, 
            [MarshalAs(UnmanagedType::LPStr)]String* szLabel);

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglBottomLabel")]
		static public long BottomLabel(
            long lRegionID, 
            [MarshalAs(UnmanagedType::LPStr)]String* szLabel);

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglTitle")]
		static public long Title(
            long lRegionID, 
            [MarshalAs(UnmanagedType::LPStr)]String* szLabel);

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglRightLabel")]
		static public long RightLabel(
            long lRegionID, 
            [MarshalAs(UnmanagedType::LPStr)]String* szLabel);

        ///<summary></summary>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglLegend")]
		static public long Legend(
            long lRegionID);

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
		[DllImport(PGLDLL_NAME, EntryPoint="pglZoomAll")]
		static public void ZoomAll(
            long lRegionID, 
            int recurse);

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        [DllImport(PGLDLL_NAME, EntryPoint="pglZoom")]
		static public void Zoom(
            long lRegionID, 
            double dLeft, 
            double dTop, 
            double dRight, 
            double dBottom);

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglGetZoom")]
		static public int  GetZoom(
			long lRegionID, 
			double* pLeft, 
			double* pBottom, 
			double* pRight, 
			double* pTop);

        ///<summary></summary>
        ///<param name=""></param>
		[DllImport(PGLDLL_NAME, EntryPoint="pglAutoZoom")]
		static public void AutoZoom(
			[MarshalAs(UnmanagedType::LPStr)]String* szState );

        ///<summary></summary>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglLoadFromXML")]
		static public long LoadFromXML(
			long lRegionID, 
			[MarshalAs(UnmanagedType::LPStr)]String* szFileName );

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglSaveToXML")]
		static public int SaveToXML(
			long lRegionID, 
			[MarshalAs(UnmanagedType::LPStr)]String* szFileName, 
			int bZipping );

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglRenderToFile")]
		static public int RenderToFile(
			long lRegionID, 
			[MarshalAs(UnmanagedType::LPStr)]String* szFileName, 
			[MarshalAs(UnmanagedType::LPStr)]String* szFormat 
			);

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglLoadCSVFile")]
		static public int LoadCSVFile( 
			long lRegionID, 
			[MarshalAs(UnmanagedType::LPStr)]String* szFileName
			);
		
        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		[DllImport(PGLDLL_NAME, EntryPoint="pglRenderToBitmap")]
		static public long RenderToByteArray(
			long lRegionID, 
			unsigned int width_,
			unsigned int height_,
			unsigned int stride_,
			unsigned int bpp_,
			char __gc* bits,
            [MarshalAs(UnmanagedType::LPStr)]String* szFormat 
			);

        static String __gc* ColorToString(System::Drawing::Color c)
        {
            using System::Text::StringBuilder;

            StringBuilder __gc* sb = new StringBuilder();
            sb->Append("rgba(");
            sb->AppendFormat("{0},{1},{2},",
                c.R.ToString(), 
                c.G.ToString(),
                c.B.ToString()
                );
            sb->AppendFormat("{0})",
                c.A.ToString()
                );
            return sb->ToString();
        }
	};

    public __value struct PglData
    {
    public:
        static float Adapt(float v __gc[] ) __gc[]
        {   
            return v;
        };
        static float Adapt(double v __gc[] ) __gc[]
        {
            if (v==0)
                throw new ArgumentNullException("collection");
            int i,n;
            n=v->get_Length();
            float v_return  __gc[] = new float __gc[n];

            for (i=0;i<n;++i)
            {
                v_return[i] = static_cast<float>(v[i]);
            }
            return v_return;
        }
        static float Adapt(int v __gc[] )__gc[] 
        {
            if (v==0)
                throw new ArgumentNullException("collection");
            int i,n;
            n=v->get_Length();
            float v_return __gc [] = new float __gc[n];

            for (i=0;i<n;++i)
            {
                v_return[i] = static_cast<float>(v[i]);
            }
            return v_return;
        }
/*
        float Adapt(System::Array __gc* a)__gc[] 
        {
            if (!a)
                throw new ArgumentNullException("array");

            int i,n;
            n=a->get_Length();
            float v_return __gc[] = new float __gc[n];

            for (i=0;i<n;++i)
            {
                v_return[i] = static_cast<float>(a->get_Item(i));
            }
            return v_return;
        }

        float  Adapt(System::Collections::ICollection __gc* col)__gc[]
        {
            if (!col)
                throw new ArgumentNullException("collection");

            int i,n;
            n=col->get_Count();
            System::Array __gc* a = new System::Array( n );

            return Adapt(a);
        }
*/
    };

    ///<summary>PGL object base</summary>
    public __gc class PglObject
    {
    public:
        ///<summary>Construct object for ID</summary>
        ///<remarks>This constructor should never be called directly</remarks>
        PglObject(long id)
        {
            m_ID = id;
        }
        
        ///<summary>ID property</summary>
        ///<returns>Identification number</returns>
        __property long get_ID() {   return m_ID;};

        ///<summary>Name property</summary>
        ///<returns>Object name</returns>
//        __property String __gc* get_Name();
        ///<summary>Set name property</summary>
        ///<param name="name">Object name</param>
        __property void set_Name(String __gc* name)
        {
            if (!name)
                throw new ArgumentNullException("name");

            Pgl::Set(get_ID(),
                String::Format(S"name=\"{0}\"",name)
                );
        };

        ///<summary>The description string is used in legends</summary>
        ///<returns>object description</returns>
//        __property String __gc* get_Description();
        ///<summary>Description set property</summary>
        ///<param name="desc">description string</param>
        __property void set_Description(String __gc* desc)
        {
            if (!desc)
                throw new ArgumentNullException("description");
            Pgl::Set(get_ID(),
                String::Format(S"description=\"{0}\"",desc)
                );
        };

        ///<summary>Object stroke color</summary>
        ///<returns>current stroke color (RGBA)</returns>
//        __property System::Drawing::Color get_Color();
        ///<summary>Set the object stroke color</summary>
        ///<param name="color">stroke color (RBGA)</param>
        __property void set_Color(System::Drawing::Color color)
        {
            String __gc* s=String::Format(
                "color={0}",Pgl::ColorToString(color)
                );

            Pgl::Set(get_ID(),s);
        };

 //       __property bool get_Visible();
        ///<summary>Set visibility state</summary>
        ///<param name="visible">true if visible</param>
        __property void set_Visible(bool visible)
        {
            if (visible)
                Pgl::Set(get_ID(),"visible=on");
            else
                Pgl::Set(get_ID(),"visible=off");
        }


        void SetBackgroundColor(System::Drawing::Color c)
        {            
            String __gc* s=String::Format("brush=\"type=solid c={0}\"",Pgl::ColorToString(c));
            Pgl::Set(get_ID(), s);
        }

        void SetBackgroundGradient(
            System::Drawing::Color startColor,
            System::Drawing::Color endColor,
            float angleDegCCW
            )
        {
            String __gc* s=String::Format("brush=\"type=lingrad startc={0}  endc={1}  angle={2}\"",
                Pgl::ColorToString(startColor),
                Pgl::ColorToString(endColor),
                angleDegCCW.ToString()
                );
            Pgl::Set(get_ID(), s);
        }

    private:
        long m_ID;
    };

    ///<summary>A line object</summary>
    public __gc class PglLine : 
        public PglObject
    {
    public:
        ///<summary>Constuct line from ID number</summary>
        ///<remarks>this method should not be called directly</remarks>
        PglLine(long id)
            : PglObject(id)
        {};

        ///<summary>Dash pattern property</summary>
        ///<returns>dash pattern (string)</returns>
        ///<remarks>dash pattern is defined as in PostScript language:
        /// it is a succession of number, describing a pen distance, alternating
        /// stroke - no stroke.
        /// For example: 3 1 1  = move 3 with stroke, move 1 without stroke,
        /// move 1 with stroke and will lead to something like - . - . -
//        __property String __gc* get_DashPattern();
        ///<summary>Set dash pattern</summary>
        ///<param name="dp">dash pattern</param>
        __property void set_DashPattern(String __gc* dp)
        {
            if (!dp)
                throw new ArgumentNullException("dash pattern");
            Pgl::Set(get_ID(),
                String::Format(S"dash=\"{0}\"",dp)
                );
        };

  //      __property bool get_Open();
        ///<summary>Set open close state</summary>
        ///<param name="open">true if open (default)</param>
        __property void set_Open(bool open)
        {
            if (open)
                Pgl::Set(get_ID(),"open=true");
            else
                Pgl::Set(get_ID(),"open=false");
        }

   //     __property bool get_Shadow();
        ///<summary>Set shadowing</summary>
        ///<param name="shadow">true to turn on shadowing</param>
        __property void set_Shadow(bool shadow)
        {
            if (shadow)
                Pgl::Set(get_ID(),"shadow=true");
            else
                Pgl::Set(get_ID(),"shadow=false");
        }

  //      __property bool get_SnapToBottom();
        ///<summary>Set snap to bottom state</summary>
        ///<param name="enable">true to snap line to bottom</param>
        __property void set_SnapToBottom(bool enable)
        {
            if (enable)
                Pgl::Set(get_ID(),"snapbottom=true");
            else
                Pgl::Set(get_ID(),"snapbottom=false");
        }

        __property void set_Width(double width)
        {
            Pgl::Set(get_ID(), 
                String::Format("width={0}",width.ToString())
                );
        }

        __property void set_Contour(bool enable)
        {
            if (enable)
                Pgl::Set(get_ID(),"contour=true");
            else
                Pgl::Set(get_ID(),"contour=false");
        }

        __value enum InterpolationType
        {
            InterpolationLinear,
            InterpolationStep,
            InterpolationSpline,
            InterpolationMultiStrip
        };

        __property void set_Interpolation(InterpolationType i)
        {
            switch(i)
            {
            case InterpolationLinear:
                Pgl::Set(get_ID(),"interpolation=linear");
                break;
            case InterpolationStep:
                Pgl::Set(get_ID(),"interpolation=step");
                break;
            case InterpolationSpline:
                Pgl::Set(get_ID(),"interpolation=spline");
                break;
            case InterpolationMultiStrip:
                Pgl::Set(get_ID(),"interpolation=multistrip");
                break;
            }
        }

        __property void set_StripSize(int i)
        {
            Pgl::Set(get_ID(),
                String::Format("stripsize={0}",i.ToString())
                );
        }

        __property void set_Tension(float tension)
        {
            Pgl::Set(get_ID(),
                String::Format("tension={0}",tension.ToString())
                );
        }

    };

    ///<summary>A axis object</summary>
    public __gc class PglAxis : public PglObject
    {
    public:
        ///<summary>Constuctor from ID number</summary>
        ///<remarks>This method should not be used directly</remarks>
        PglAxis(long id)
            : PglObject(id)
        {};
    };

    public __gc class PglObjectEnumerator;
    public __gc class PglChildEnumerator;

    ///<summary>A region object</summary>
    ///<remarks>A region is a container for object and child regions,
    ///is contains an axis.</remarks>
    public __gc class PglRegion : 
        public PglObject
    {
    public:
        ///<summary>Constuct region from ID number</summary>
        ///<remarks>This method should not be used directly</remarks>
        PglRegion(long id)
        : PglObject(id)
        {};

        ///<summary>Creates a new region object</summary>
        ///<returns>new region</returns>
        static PglRegion __gc* Create()
        {
            return new PglRegion( Pgl::Region());
        }

        ///<summary>Returns current region</summary>
        ///<returns>current region object</returns>
        __property static PglRegion __gc* get_Current()
        {
            return new PglRegion( Pgl::GetCR() );
        }

        ///<summary>Returns axis</summary>
        ///<returns>axis object</returns>
  //      __property PglAxis __gc* get_Axis();

        ///<summary>number of objects</summary>
        ///<returns>number of objects</returns>
        __property int get_ObjectLength()
        {
            return Pgl::GetObjectsSize(get_ID());
        };

        ///<summary>object accessor</summary>
        ///<returns>i-th object</returns>
        PglObject __gc* ObjectItem(int i)
        {
            return new PglObject(Pgl::GetObject(get_ID(),i));
        }

        ///<summary>removes object</summary>
        ///<param name="o">object to remove</param>
        void RemoveObject(PglObject __gc* o)
        {
            if (!o)
                throw new ArgumentNullException("object");
            Pgl::RemoveObject(get_ID(),o->get_ID());
        };
/*
        __property PglObjectEnumerator __gc* get_Objects()
        {
            return new PglObjectEnumerator( this );
        }

        __property PglChildEnumerator __gc* get_Children()
        {
            return new PglChildEnumerator( this );
        }
*/
        ///<summary>number of childs</summary>
        ///<returns>number of childs</returns>
        __property int get_ChildLength()
        {
            return Pgl::GetChildrenSize(get_ID());
        }
        ///<summary>Child accessor</summary>
        ///<returns>return i-th child</returns>
        PglRegion __gc* ChildItem(int i)
        {
            return new PglRegion( Pgl::GetChild(get_ID(),static_cast<long>(i)));
        }
        ///<summary>Removes a child</summary>
        ///<param name="c">child to remove</param>
        void RemoveChild(PglRegion __gc* c)
        {
            if (!c)
                throw new ArgumentNullException("child");
            Pgl::RemoveChild(get_ID(),c->get_ID());
        }
        ///<summary>Get parent region</summary>
        ///<returns>parent region</returns>
        __property PglRegion __gc* get_Parent()
        {
            return new PglRegion( Pgl::GetParent(ID));
        }

        ///<summary>Sets the axis left label</summary>
        ///<param name="label">left label</param>
        __property void set_LeftLabel(String __gc* label)
        {
            if (!label)
                throw new ArgumentNullException("label is 0");
            Pgl::LeftLabel(get_ID(), label);
        }
        ///<summary>Sets the axis right label</summary>
        ///<param name="right">right label</param>
        __property void set_RightLabel(String __gc* label)
        {
            if (!label)
                throw new ArgumentNullException("label is 0");
            Pgl::RightLabel(get_ID(), label);
        }

        ///<summary>Sets the title</summary>
        ///<param name="title">title label</param>
        __property void set_Title(String __gc* label)
        {
            if (!label)
                throw new ArgumentNullException("label is 0");
            Pgl::Title(get_ID(), label);
        }

        ///<summary>Sets the axis bottom label</summary>
        ///<param name="label">bottom label</param>
        __property void set_BottomLabel(String __gc* label)
        {
            if (!label)
                throw new ArgumentNullException("label is 0");
            Pgl::BottomLabel(get_ID(), label);
        }

        ///<summary>Divides the region in a sub-region matrix</summary>
        ///<param name="Rows">number of child rows</param>
        ///<param name="Columns">number of child columns</param>
        void Divide(int Rows, int Columns)
        {
            Pgl::Divide(get_ID(), Rows, Columns);
        }

        ///<summary>Divides region in a complex layout</summary>
        ///<param name="xml">layout xml description</param>
        void Layout(System::Xml::XmlNode __gc* xml)
        {
            if (!xml)
                throw new ArgumentNullException("layout xml");
            Pgl::Layout(get_ID(),xml->ToString());
        }

        ///<summary>Adds a legend</summary>
        void AddLegend()
        {
            Pgl::Legend(get_ID());
        }

        ///<summary>Zooms region</summary>
        ///<param name="rect">World coordinates to zoom</param>
        __property void set_Zoom(System::Drawing::RectangleF rect)
        {
            Pgl::Zoom(get_ID(),
                rect.Left,
                rect.Top,
                rect.Right,
                rect.Bottom
                );
        };
        ///<summary>Get chart extent</summary>
        ///<returns>chart extent</returns>
        __property System::Drawing::RectangleF get_Zoom()
        {
            double l,r,b,t;
            Pgl::GetZoom(get_ID(),&l,&b,&r,&t);
            return System::Drawing::RectangleF(
                static_cast<float>(l),
                static_cast<float>(t),
                static_cast<float>(r-l),
                static_cast<float>(t-b)
                );
        }
        ///<summary>Zooms extent of chart</summary>
        ///<param name="recurse">if true, applies zoom all to childs</param>
        void ZoomAll(bool recurse)
        {
            Pgl::ZoomAll(get_ID(), static_cast<int>(recurse));
        };
        ///<summary>Get the automatic zoomall state</summary>
        ///<returns>true if on, false otherwize</returns>
        // __property static bool get_AutoZoom();
        ///<summary>Sets the automatic zoomall state</summary>
        __property static void set_AutoZoom(bool az)
        {
            if (az)
                Pgl::AutoZoom("on");
            else
                Pgl::AutoZoom("off");
        };

        ///<summary>Close and destroys the region</summary>
        void Close()
        {
            Pgl::CloseRegion(get_ID());
        };

        ///<summary>Close and destroys all opened regions</summary>
        static void CloseAllRegions()
        {
            Pgl::CloseAllRegions();
        };

        ///<summary>Plot data as a polyline</summary>
        ///<param name="x">x positions array</param>
        ///<param name="y">y positions array</param>
        ///<param name="flags"></param>
        ///<returns>polyline object</returns>
		PglLine __gc* Plot(
			float  x __gc[],
			float y __gc[], 
			String __gc* flags
            )
        {
            if (x==0)
                throw new ArgumentNullException("x array");
            if (y==0)
                throw new ArgumentNullException("y array");
            if (flags == 0)
                flags = new System::String("");

            int n = System::Math::Min(x->get_Length(), y->get_Length());
            return new PglLine(
                    Pgl::Plot(
                        get_ID(),
                        n,
                        x,
                        y,
                        flags,
                        true
                        )
                );
        }

        PglLine __gc* Plot(
            int length,
            System::IntPtr x,
            System::IntPtr y, 
            String __gc* flags,
            bool makeCopy
            )
        {
            if (x==0)
                throw new ArgumentNullException("x array");
            if (y==0)
                throw new ArgumentNullException("y array");
            if (flags == 0)
                flags = new System::String("");

            return new PglLine(
                Pgl::Plot(
                get_ID(),
                length,
                PTR2FLOATPTR(x),
                PTR2FLOATPTR(y),
                flags,
                makeCopy
                )
                );
        }

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		PglLine __gc* PlotY(
			float x0, 
            float xStep,
			float y __gc[], 
			String __gc* flags)
        {
            if (y==0)
                throw new ArgumentNullException("y array");
            if (flags == 0)
                flags = new System::String("");

            int n = y->get_Length();
            return new PglLine(
                    Pgl::PlotY(
                        get_ID(),
                        y->get_Length(),
                        x0,
                        xStep,
                        y,
                        flags,
                        true
                        )
                );
        }

        PglLine __gc* PlotY(
            int length,
            float x0, 
            float xStep,
            System::IntPtr y, 
            String __gc* flags,
            bool makeCopy
            )
        {
            if (y==0)
                throw new ArgumentNullException("y array");
            if (flags == 0)
                flags = new System::String("");

            return new PglLine(
                Pgl::PlotY(
                get_ID(),
                length,
                x0,
                xStep,
                PTR2FLOATPTR(y),
                flags,
                makeCopy
                )
                );
        }

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		PglLine __gc* PlotLOD(
			float x  __gc[],
			float y __gc[], 
			float compressionRatio, 
			String __gc* flags)
        {
            if (x==0)
                throw new ArgumentNullException("x array");
            if (y==0)
                throw new ArgumentNullException("y array");
            if (flags == 0)
                flags = new System::String("");

            int n = System::Math::Min(x->get_Length(), y->get_Length());
            return new PglLine(
                    Pgl::PlotLOD(
                        get_ID(),
                        n,
                        x,
                        y,
                        compressionRatio,
                        flags,
                        true
                        )
                );
        }

        PglLine __gc* PlotLOD(
            int length,
            System::IntPtr x,
            System::IntPtr y, 
            float compressionRatio, 
            String __gc* flags,
            bool makeCopy)
        {
            if (length<2)
                throw new ArgumentNullException("not enough points");
            if (x==0)
                throw new ArgumentNullException("x array");
            if (y==0)
                throw new ArgumentNullException("y array");
            if (flags == 0)
                flags = new System::String("");

            return new PglLine(
                Pgl::PlotLOD(
                get_ID(),
                length,
                PTR2FLOATPTR(x),
                PTR2FLOATPTR(y),
                compressionRatio,
                flags,
                makeCopy
                )
                );
        }

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		PglLine __gc* PlotLODY(
			float x0, 
			float xStep,
			float y __gc[] , 
			float compressionRatio, 
			String __gc* flags)
        {
            if (y==0)
                throw new ArgumentNullException("y array");
            if (flags == 0)
                flags = new System::String("");

            int n = y->get_Length();
            return new PglLine(
                    Pgl::PlotLODY(
                        get_ID(),
                        n,
                        x0,
                        xStep,
                        y,
                        compressionRatio,
                        flags,
                        true
                        )
                );
        }

        PglLine __gc* PlotLODY(
            int length,
            float x0, 
            float xStep,
            System::IntPtr y, 
            float compressionRatio, 
            String __gc* flags,
            bool makeCopy
            )
        {
            if (y==0)
                throw new ArgumentNullException("y array");
            if (flags == 0)
                flags = new System::String("");

            return new PglLine(
                Pgl::PlotLODY(
                get_ID(),
                length,
                x0,
                xStep,
                PTR2FLOATPTR(y),
                compressionRatio,
                flags,
                makeCopy
                )
                );
        }

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		PglLine __gc* PlotFcn(
			float x __gc[], 
			String __gc* fcn,
			String __gc* flags
            )
        {
            if (x==0)
                throw new ArgumentNullException("x array");
            if (fcn==0)
                throw new ArgumentNullException("function description");
            if (flags == 0)
                flags = new System::String("");

            int n = x->get_Length();
            return new PglLine(
                    Pgl::PlotFcn(
                        get_ID(),
                        n,
                        x,
                        fcn,
                        flags,
                        true
                        )
                );
        }

        PglLine __gc* PlotFcn(
            int length,
            System::IntPtr x, 
            String __gc* fcn,
            String __gc* flags,
            bool makeCopy
            )
        {
            if (x==0)
                throw new ArgumentNullException("x array");
            if (fcn==0)
                throw new ArgumentNullException("function description");
            if (flags == 0)
                flags = new System::String("");

            return new PglLine(
                Pgl::PlotFcn(
                get_ID(),
                length,
                PTR2FLOATPTR(x),
                fcn,
                flags,
                makeCopy
                )
                );
        }

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		PglLine __gc* PlotFcnY(
            int n,
			float x0,
            float xStep,
			String __gc* fcn,
			String __gc* flags
            )
        {
            if (fcn==0)
                throw new ArgumentNullException("function description");
            if (flags == 0)
                flags = new System::String("");

            return new PglLine(
                    Pgl::PlotFcnY(
                        get_ID(),
                        n,
                        x0,
                        xStep,
                        fcn,
                        flags,
                        true
                        )
                );
        }

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		PglLine __gc* PlotHor(
			float y, 
			String __gc* flags
            )
        {
            if (flags == 0)
                flags = new System::String("");

            return new PglLine(
                    Pgl::PlotHor(
                        get_ID(),
                        y,
                        flags
                        )
                );
        }

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		PglLine __gc* PlotVer(
			float x, 
			String __gc* flags
            )
        {
            if (flags == 0)
                flags = new System::String("");

            return new PglLine(
                    Pgl::PlotVer(
                        get_ID(),
                        x,
                        flags
                        )
                );
        }

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		PglLine __gc* Histogram(
			float data __gc[], 
			String __gc* flags
            )
        {
            if (data==0)
                throw new ArgumentNullException("data array");
            if (flags == 0)
                flags = new System::String("");

            int n = data->get_Length();
            return new PglLine(
                    Pgl::Histogram(
                        get_ID(),
                        n,
                        data,
                        flags,
                        true
                        )
                );
       }

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
        PglLine __gc* Histogram(
            int length,
            System::IntPtr data, 
            String __gc* flags,
            bool makeCopy
            )
        {
            if (data==0)
                throw new ArgumentNullException("data array");
            if (flags == 0)
                flags = new System::String("");

            return new PglLine(
                Pgl::Histogram(
                get_ID(),
                length,
                PTR2FLOATPTR(data),
                flags,
                makeCopy
                )
                );
        }

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		PglLine __gc* ErrorBar(
			float x __gc[],
			float y __gc[],
			float errorUp __gc[],
			float errorDown __gc[], 
		    String __gc* flags
            )
        {
            if (x==0)
                throw new ArgumentNullException("x array");
            if (y==0)
                throw new ArgumentNullException("y array");
            if (errorDown==0)
                throw new ArgumentNullException("error down");
            if (errorUp==0)
                throw new ArgumentNullException("error up");
            if (flags == 0)
                flags = new System::String("");

            int n = System::Math::Min(x->get_Length(), y->get_Length());
            n=System::Math::Min(n, errorUp->get_Length());
            n=System::Math::Min(n, errorDown->get_Length());
            return new PglLine(
                    Pgl::ErrorBar(
                        get_ID(),
                        n,
                        x,
                        y,
                        errorUp,
                        errorDown,
                        flags,
                        true
                        )
                );
        }

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
        PglLine __gc* ErrorBar(
            int length,
            System::IntPtr x,
            System::IntPtr y,
            System::IntPtr errorUp,
            System::IntPtr errorDown, 
            String __gc* flags,
            bool makeCopy
            )
        {
            if (x==0)
                throw new ArgumentNullException("x array");
            if (y==0)
                throw new ArgumentNullException("y array");
            if (errorDown==0)
                throw new ArgumentNullException("error down");
            if (errorUp==0)
                throw new ArgumentNullException("error up");
            if (flags == 0)
                flags = new System::String("");

            return new PglLine(
                Pgl::ErrorBar(
                get_ID(),
                length,
                PTR2FLOATPTR(x),
                PTR2FLOATPTR(y),
                PTR2FLOATPTR(errorUp),
                PTR2FLOATPTR(errorDown),
                flags,
                makeCopy
                )
                );
        }

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		PglLine __gc* ErrorBarY(
			float x0, 
			float xStep,
			float y __gc[],
			float errorUp __gc[],
			float errorDown __gc[], 
		    String __gc* flags
            )
        {
            if (y==0)
                throw new ArgumentNullException("y array");
            if (errorDown==0)
                throw new ArgumentNullException("error down");
            if (errorUp==0)
                throw new ArgumentNullException("error up");
            if (flags == 0)
                flags = new System::String("");

            int n=System::Math::Min(y->get_Length(), errorUp->get_Length());
            n=System::Math::Min(n, errorDown->get_Length());
            return new PglLine(
                    Pgl::ErrorBarY(
                        get_ID(),
                        n,
                        x0,
                        xStep,
                        y,
                        errorUp,
                        errorDown,
                        flags,
                        true
                        )
                );
        }

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
        PglLine __gc* ErrorBarY(
            int length,
            float x0, 
            float xStep,
            System::IntPtr y,
            System::IntPtr errorUp,
            System::IntPtr errorDown, 
            String __gc* flags,
            bool makeCopy)
        {
            if (y==0)
                throw new ArgumentNullException("y array");
            if (errorDown==0)
                throw new ArgumentNullException("error down");
            if (errorUp==0)
                throw new ArgumentNullException("error up");
            if (flags == 0)
                flags = new System::String("");

            return new PglLine(
                Pgl::ErrorBarY(
                get_ID(),
                length,
                x0,
                xStep,
                PTR2FLOATPTR(y),
                PTR2FLOATPTR(errorUp),
                PTR2FLOATPTR(errorDown),
                flags,
                makeCopy
                )
                );
        }

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		PglObject __gc* Scatter(
			float x __gc[],
			float y __gc[],
			float values __gc[], 
			String __gc* flags
            )
        {
            if (x==0)
                throw new ArgumentNullException("x array");
            if (y==0)
                throw new ArgumentNullException("y array");
            if (values==0)
                throw new ArgumentNullException("error down");
            if (flags == 0)
                flags = new System::String("");

            int n = System::Math::Min(x->get_Length(), y->get_Length());
            n=System::Math::Min(n, values->get_Length());
            return new PglObject(
                    Pgl::Scatter(
                        get_ID(),
                        n,
                        x,
                        y,
                        values,
                        flags,
                        true
                        )
                );
        }

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
        PglObject __gc* Scatter(
            int length,
            System::IntPtr x,
            System::IntPtr y,
            System::IntPtr values, 
            String __gc* flags,
            bool makeCopy
            )
        {
            if (x==0)
                throw new ArgumentNullException("x array");
            if (y==0)
                throw new ArgumentNullException("y array");
            if (values==0)
                throw new ArgumentNullException("error down");
            if (flags == 0)
                flags = new System::String("");

            return new PglObject(
                Pgl::Scatter(
                get_ID(),
                length,
                PTR2FLOATPTR(x),
                PTR2FLOATPTR(y),
                PTR2FLOATPTR(values),
                flags,
                makeCopy
                )
                );
        }

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		PglLine __gc* Stock(
			float x0, 
			float xStep,
			float open __gc[],
			float high __gc[],
			float low __gc[],
			float close __gc[], 
			String __gc* flags
            )
        {
            if (open==0)
                throw new ArgumentNullException("open array");
            if (high==0)
                throw new ArgumentNullException("high array");
            if (low==0)
                throw new ArgumentNullException("low array");
            if (close==0)
                throw new ArgumentNullException("close array");
            if (flags == 0)
                flags = new System::String("");

            int n = System::Math::Min(open->get_Length(), high->get_Length());
            n=System::Math::Min(n, low->get_Length());
            n=System::Math::Min(n, close->get_Length());
            return new PglLine(
                    Pgl::Stock(
                        get_ID(),
                        n,
                        x0,
                        xStep,
                        open,
                        high,
                        low,
                        close,
                        flags,
                        true
                        )
                );
        }

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
        PglLine __gc* Stock(
            int length,
            float x0, 
            float xStep,
            System::IntPtr open,
            System::IntPtr high,
            System::IntPtr low,
            System::IntPtr close, 
            String __gc* flags,
            bool makeCopy
            )
        {
            if (open==0)
                throw new ArgumentNullException("open array");
            if (high==0)
                throw new ArgumentNullException("high array");
            if (low==0)
                throw new ArgumentNullException("low array");
            if (close==0)
                throw new ArgumentNullException("close array");
            if (flags == 0)
                flags = new System::String("");

            return new PglLine(
                Pgl::Stock(
                get_ID(),
                length,
                x0,
                xStep,
                PTR2FLOATPTR(open),
                PTR2FLOATPTR(high),
                PTR2FLOATPTR(low),
                PTR2FLOATPTR(close),
                flags,
                makeCopy
                )
                );
        }

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		PglLine __gc* CandleStick(
			float x0, 
			float xStep,
			float open __gc[],
			float high __gc[],
			float low __gc[],
			float close __gc[], 
			String __gc* flags
            )
        {
            if (open==0)
                throw new ArgumentNullException("open array");
            if (high==0)
                throw new ArgumentNullException("high array");
            if (low==0)
                throw new ArgumentNullException("low array");
            if (close==0)
                throw new ArgumentNullException("close array");
            if (flags == 0)
                flags = new System::String("");

            int n = System::Math::Min(open->get_Length(), high->get_Length());
            n=System::Math::Min(n, low->get_Length());
            n=System::Math::Min(n, close->get_Length());
            return new PglLine(
                    Pgl::CandleStick(
                        get_ID(),
                        n,
                        x0,
                        xStep,
                        open,
                        high,
                        low,
                        close,
                        flags,
                        true
                        )
                );
        }

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
        PglLine __gc* CandleStick(
            int length,
            float x0, 
            float xStep,
            System::IntPtr open,
            System::IntPtr high,
            System::IntPtr low,
            System::IntPtr close, 
            String __gc* flags,
            bool makeCopy)
        {
            if (open==0)
                throw new ArgumentNullException("open array");
            if (high==0)
                throw new ArgumentNullException("high array");
            if (low==0)
                throw new ArgumentNullException("low array");
            if (close==0)
                throw new ArgumentNullException("close array");
            if (flags == 0)
                flags = new System::String("");

            return new PglLine(
                Pgl::CandleStick(
                get_ID(),
                length,
                x0,
                xStep,
                PTR2FLOATPTR(open),
                PTR2FLOATPTR(high),
                PTR2FLOATPTR(low),
                PTR2FLOATPTR(close),
                flags,
                makeCopy
                )
                );
        }
    };

    public __gc class PglObjectEnumerator : public System::Collections::IEnumerator
        {
        private:
            PglRegion __gc* m_region;
            int m_i;
            int m_length;

        public:
            PglObjectEnumerator(PglRegion __gc* region)
            {
                if (!region)
                    throw new ArgumentNullException("region is null");
                m_region=region;
                m_i=-1;
                m_length = m_region->get_ObjectLength();
            }

            __property Object __gc* get_Current()
            {
                 if (m_i<0 || m_i>=m_length)
                        throw new System::InvalidOperationException("enumerator out of bounds");

                    return m_region->ObjectItem(m_i);
            }
            bool MoveNext()
            {
                ++m_i;
                return m_i < m_length;
            }
            void Reset()
            {
                m_i=-1;
            }
        };

    public __gc class PglChildEnumerator : public System::Collections::IEnumerator
    {
    private:
        PglRegion __gc* m_region;
        int m_i;
        int m_length;

    public:
        PglChildEnumerator(PglRegion __gc* region)
        {
            if (!region)
                throw new ArgumentNullException("region is null");
            m_region=region;
            m_i=-1;
            m_length = m_region->get_ChildLength();
        }

        __property Object __gc* get_Current()
        {
           if (m_i<0 || m_i>=m_length)
                    throw new System::InvalidOperationException("enumerator out of bounds");

                return m_region->ChildItem(m_i);
        }            

        bool MoveNext()
        {
            ++m_i;
            return m_i < m_length;
        }
        void Reset()
        {
            m_i=-1;
        }
    };


    ///<summary></summary>
    public __value struct Serializer
    {
        ///<summary></summary>
        ///<param name=""></param>
        ///<returns></returns>
		static PglRegion __gc* LoadFromXML(
            PglRegion __gc* region,
			String __gc* fileName 
            )
        {
            if (!region)
                throw new ArgumentNullException("Region");
            if (!fileName)
                throw new ArgumentNullException("fileName");

            if (Pgl::LoadFromXML(region->get_ID(),fileName) < 0)
                throw new Exception("LoadFromXML failed");

            return region;
        }

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		static public void SaveToXML(
            PglRegion __gc* region,
			String __gc* fileName, 
			bool zipping 
            )
        {
            if (!region)
                throw new ArgumentNullException("Region");
            if (!fileName)
                throw new ArgumentNullException("fileName");

            if (Pgl::SaveToXML(region->get_ID(),fileName,zipping) < 0)
                throw new Exception("SaveToXML failed");
        }

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		static public void RenderToFile(
            PglRegion __gc* region,
			String __gc* fileName, 
			String __gc* format 
			)
        {
            if (!region)
                throw new ArgumentNullException("Region");
            if (!fileName)
                throw new ArgumentNullException("fileName");
            if (!format)
                throw new ArgumentNullException("format");

            if (Pgl::RenderToFile(region->get_ID(),fileName,format) < 0)
                throw new Exception("RenderToFile failed");
        }

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<returns></returns>
		static public void LoadCSVFile( 
            PglRegion __gc* region,
			String __gc* fileName
			)
        {
            if (!region)
                throw new ArgumentNullException("Region");
            if (!fileName)
                throw new ArgumentNullException("fileName");
        
            if (Pgl::LoadCSVFile(region->get_ID(),fileName) < 0)
                throw new Exception("LoadCSVFile failed");
        }

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
		static void RenderToStream(
            PglRegion __gc* region,
			int width,
			int height,
			System::Drawing::Imaging::PixelFormat pixelFormat,
			System::Drawing::Imaging::ImageFormat* imageFormat,
			System::IO::Stream __gc* stream,
            String __gc* flags
			)
        {
            if (!region)
                throw new ArgumentNullException("Region");
            if (!imageFormat)
                throw new ArgumentNullException("imageFormat");
            if (!stream)
                throw new ArgumentNullException("stream");
            if (!flags)
                flags = new String("");

			System::Drawing::Bitmap __gc* bmp = new System::Drawing::Bitmap(
				width,
				height,
				pixelFormat);

			if (!bmp)
				throw new System::Exception("Could not create bitmap");

			RenderToBitmap(region,bmp,flags);
			
			bmp->Save(stream,imageFormat);
		}

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
		static void RenderToResponse(
            PglRegion __gc* region,
			int width,
			int height,
			System::Drawing::Imaging::PixelFormat pixelFormat,
			System::Drawing::Imaging::ImageFormat* imageFormat,
			System::Web::HttpResponse __gc* httpResponse,
            String __gc* flags
			)
        {
			using System::IO::MemoryStream;
            using namespace System::Drawing::Imaging;
            if (!region)
                throw new ArgumentNullException("Region");
            if (!imageFormat)
                throw new ArgumentNullException("imageFormat");
            if (!httpResponse)
                throw new ArgumentNullException("httpResponse");
            if (!flags)
                flags = new String("");

			MemoryStream __gc* mem = new MemoryStream();
			RenderToStream(
				region,
				width,
				height,
				pixelFormat,
				imageFormat,
				mem,
                flags
				);


            String __gc* mime;
            if( imageFormat == ImageFormat::Png )
                mime = new String("image/png");
            else if (imageFormat == ImageFormat::Gif )
                mime = new String("image/gif");
            else if (imageFormat == ImageFormat::Jpeg )
                mime = new String("image/jpeg");
            else
                mime = new String("text");

			httpResponse->ClearContent();
			httpResponse->set_ContentType(mime);
			httpResponse->BinaryWrite(mem->ToArray());
			httpResponse->Flush();
		};

        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
		static void RenderToBitmap(
            PglRegion __gc* region,
			System::Drawing::Bitmap __gc* bitmap,
            String __gc* flags
			)
        {
            if (!region)
                throw new ArgumentNullException("Region");
            if (!bitmap)
                throw new ArgumentNullException("bitmap");
            if (!flags)
                flags = new String("");

			System::Drawing::Imaging::BitmapData __gc* data=bitmap->LockBits(
				System::Drawing::Rectangle(
					0,
					0,
					bitmap->get_Width(),
					bitmap->get_Height()),
					System::Drawing::Imaging::ImageLockMode::WriteOnly,
					bitmap->get_PixelFormat()
				);

			RenderToBitmapData(
				region,
				data,
                flags
				);
			bitmap->UnlockBits(data);
		};


        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
		static void RenderToBitmapData(
            PglRegion __gc* region,
			System::Drawing::Imaging::BitmapData __gc* data,
            String __gc* flags
			)
        {
            if (!region)
                throw new ArgumentNullException("Region");
            if (!data)
                throw new ArgumentNullException("data");

			unsigned int bpp(0);
			switch( data->get_PixelFormat())
			{
			case System::Drawing::Imaging::PixelFormat::Format8bppIndexed: 
					bpp=8; break;
			case System::Drawing::Imaging::PixelFormat::Format16bppRgb555: 
					bpp=16; break;
			case System::Drawing::Imaging::PixelFormat::Format32bppArgb:
					bpp=32; break;
			case System::Drawing::Imaging::PixelFormat::Format24bppRgb: 
					bpp=24; break;
			default:
				throw new Exception("pixel format not supported");
			}

			int result = Pgl::RenderToByteArray(
				region->get_ID(),
				static_cast<unsigned int>(data->get_Width()),
				static_cast<unsigned int>(data->get_Height()),
				static_cast<unsigned int>(data->get_Stride()),
				static_cast<unsigned int>(bpp),
				PTR2CHR(data->get_Scan0()),
                flags
				);

			if (result< 0)
				throw new Exception("rendering to bitmap failed");
		};


        ///<summary></summary>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        ///<param name=""></param>
        static void RenderToGraphics(
            PglRegion __gc* region,
            int width_,
            int height_,
            System::Drawing::Graphics __gc* g,
            String __gc* flags
            )
        {
            if (!region)
                throw new ArgumentNullException("Region");
            if (!g)
                throw new ArgumentNullException("graphics");
            if (!flags)
                flags = new String("");

            System::Drawing::Bitmap __gc* bmp( 
                new System::Drawing::Bitmap(width_,height_,g)
                );

            RenderToBitmap(
                region,
                bmp,
                flags
                );
        }    
};
};